import React, {useEffect, useState,} from 'react'

// utils
const log = console.log.bind(console)

const isFalse = (value) => {
    const arr = [false, undefined, null,]
    return arr.includes(value)
}


class TreeSelect extends React.Component {

    constructor(props) {
        super(props);
        this.state = {
            data: [],
        }
    }

    componentDidMount() {
        const data = this.initData(this.props.data)
        this.setState({
            data,
        })
    }

    initData = (data, depth = 0, parentId = '') => {
        // 初始化数据
        const newData = [...data].map((value, index) => {
            value.checked = false

            // 如果没有对应的 pid id 的话清洗数据
            const pid = value.pid
            const id = value.id
            if (isFalse(pid)) {

                if (parentId) {
                    value.pid = `${parentId}`
                } else {
                    value.pid = `${depth}`
                }
            }
            if (isFalse(id)) {
                if (parentId) {
                    value.id = `${parentId}${depth}${index}`
                } else {
                    value.id = `${depth}${index}`
                }
            }

            if (value.children) {
                value.children = this.initData(value.children, depth + 1, value.id,)
            }

            return value
        })

        if (depth === 0) console.log(newData)
        return newData
    }

    // 改变所有子元素状态
    doCheckAllChildren = (array, value) => {
        const result = [...array].map(data => {
            data.checked = value
            if (data.children) {
                data.children = this.doCheckAllChildren(data.children, value)
            }
            return data
        })
        return result
    }

    // 根据id遍历树形结构并且更新状态
    findChildAndUpdate = (id, array) => {

        if (array === undefined) return

        const index = array.findIndex(c => c.id === id)
        const newData = [...array]

        if (index === -1) {
            for (let i = 0; i < array.length; i++) {
                let data = array[i]
                let children = data.children
                data = {
                    ...data,
                    children: this.findChildAndUpdate(id, children,)
                }
            }
        } else {
            const checked = newData[index].checked
            const children = newData[index].children
            newData[index].checked = !checked
            if (children) {
                newData[index].children = this.doCheckAllChildren(children, !checked)
            }
        }

        return newData
    }

    // 获取字节点状态
    childCheckValue = (data) => {
        const allChecked = data.children.every(d => d.checked)
        const allUnChecked = data.children.every(d => d.checked === false)
        if (allChecked) {
            return true
        } else if (allUnChecked) {
            return false
        } else {
            return data.checked
        }
    }

    // 遍历树检查子元素状态并改变夫元素状态
    checkChildChecked = (array) => {
        const newData = [...array].map(data => {
            const children = data.children
            if (children === undefined) return data
            data.checked = this.childCheckValue(data)
            if (data.children) {
                data.children = this.checkChildChecked(data.children)
                data.checked = this.childCheckValue(data)
            }
            return data
        })
        return newData
    }

    // 调用函数
    onCheck = (childData) => {
        let newData = this.findChildAndUpdate(childData.id, this.state.data)
        newData = this.checkChildChecked(newData)
        this.setState({
            data: newData,
        })
    }

    render() {
        return <CheckboxList
            dataList={this.state.data}
            onCheck={this.onCheck}
        />
    }


}
const CheckboxList = (props) => {
    const data = props.dataList
    return <ul>
        {data.map(value => <Checkbox value={value} key={value.id} onCheck={props.onCheck}/>)}
    </ul>
}

const Checkbox = props => {
    const [show, setShow,] = useState(true)
    const value = props.value
    const {
        children,
        title,
        checked,
    } = value

    const isFather = children && children.length > 0
    const childrenTemplate = isFather
        ? <CheckboxList dataList={children} onCheck={props.onCheck} />
        : null

    return <li
        key={title}
        style={{margin: '12px',}}
    >
        <input
            type="checkbox"
            checked={checked}
            onChange={(e) => props.onCheck(value, !checked)}
        />
        <span onClick={() => {setShow(!show)}}>{title}</span>
        {show ? childrenTemplate : null}
    </li>
}


export default TreeSelect